import { Callout } from 'nextra/components'
import BadgeGroup, { UniverTypes } from '@/components/BadgeGroup'
import Sandbox from '@/components/Sandbox'

import entryFile from './custom-canvas/demo-1/index.txt'
import mainExtensionTs from './custom-canvas/demo-1/main-extension.txt'
import columnHeaderExtensionTs from './custom-canvas/demo-1/column-header-extension.txt'
import rowHeaderExtensionTs from './custom-canvas/demo-1/row-header-extension.txt'

# 扩展 Canvas

<BadgeGroup values={[UniverTypes.SHEET]} value={UniverTypes.SHEET} />

<Sandbox
  entryFile={entryFile}
  files={{
    'main-extension.ts': mainExtensionTs,
    'column-header-extension.ts': columnHeaderExtensionTs,
    'row-header-extension.ts': rowHeaderExtensionTs,
  }}
/>

Univer 部分元素的渲染，如边框和背景，就是使用扩展机制来完成的。Facade 内置了常用扩展注册 API：

- 中间内容区域：`registerSheetMainExtension`
- 行标题：`registerSheetRowHeaderExtension`
- 列标题：`registerSheetColumnHeaderExtension`

继承 `SheetExtension` 后，提供唯一键值、层级、绘制逻辑就能实现一个 Sheet 渲染扩展。如下：

```ts
class RowHeaderCustomExtension extends SheetExtension {
  override uKey = 'RowHeaderCustomExtension'

  // 必须大于 10
  override get zIndex() {
    return 11
  }

  override draw(ctx: UniverRenderingContext, parentScale: IScale, spreadsheetSkeleton: SpreadsheetSkeleton) {
    // ... 主要的渲染逻辑
  }
}

SheetRowHeaderExtensionRegistry.add(new RowHeaderCustomExtension())
```

<Callout type="info" emoji="ℹ️">
  行标题、列标题的扩展 zIndex 必须大于 10，中间内容区域的扩展 zIndex 必须大于 50，否则会被覆盖。
</Callout>

然后注册到指定的 unitId 上：

```ts
univerAPI.registerSheetRowHeaderExtension(unitId, new RowHeaderCustomExtension())
```

值得注意的是，`UniverRenderingContext` 本质上就是 [CanvasRenderingContext2D](https://developer.mozilla.org/zh-CN/docs/Web/API/CanvasRenderingContext2D)，你可以根据自己的需求（例如先清空原有的行、列标题）来进行绘制。

在线案例参考：[Render Extension](/playground?title=Render%20Extension)
